常见的代码生成器有 MyBatis 的代码生成器，这些代码生成器主要通过下面两条 SQL 实现。

```sql
SHOW TABLE STATUS FROM order_center;  # 获取数据库下所有的表，将其转换为 entity
SHOW FULL COLUMNS FROM order_item; # 获取一张表的所有属性
```
<img src="https://wkq-img.oss-cn-chengdu.aliyuncs.com/20241215131418.png"/>

## 要实现的代码生成器
只关心对象建模，不关心数据库，根据对象建模，将相应的 mapper ，request、feign 等生成。

<img src="https://wkq-img.oss-cn-chengdu.aliyuncs.com/20241215133145.png"/>

<img src="https://wkq-img.oss-cn-chengdu.aliyuncs.com/20241215133202.png"/>


这里不再从数据库取数据源，而是从 领域对象中 取。

<img src="https://wkq-img.oss-cn-chengdu.aliyuncs.com/20241215133911.png"/>

根据注解，拿到 class，然后找到 class 里面的 field ，field 里面根据元信息，通过 javapoet 生成。
```xml
<!-- https://mvnrepository.com/artifact/com.squareup/javapoet -->
<dependency>
    <groupId>com.squareup</groupId>
    <artifactId>javapoet</artifactId>
    <version>1.13.0</version>
</dependency>

```
还需要加一些生成类所需的依赖,比如 mapstruct、spring-boot-starter-web、openfeign 等

```xml
<!-- https://mvnrepository.com/artifact/org.mapstruct/mapstruct -->
<dependency>
    <groupId>org.mapstruct</groupId>
    <artifactId>mapstruct</artifactId>
    <version>1.6.3</version>
</dependency>
```
还用到了 auto-service 做了一个自动实现 SPI。


```xml
<!-- https://mvnrepository.com/artifact/com.google.auto.service/auto-service -->
<dependency>
    <groupId>com.google.auto.service</groupId>
    <artifactId>auto-service</artifactId>
    <version>1.1.1</version>
</dependency>

```

## 实现原理

我要生成代码，这个需求抽象化出一个接口 CodeGenProcessor, 里面方法如下：
* 解析要处理类上的注解，（那个注解标记的类）
* 获取生成的包路径， （生成到哪里）
* 目标类代码生成， （开始生成）


Service 生成逻辑比较复杂，依赖 Repository 、Creator 、Updator，这时候生成就需要有一个条件了，将所有要生成的内容都放入一个上下文里面。
生成 Service 的时候需要判断是否配置这些内容，从而判断是否去生成。

这样处理的原因是，注解随时是可以删除的，为了删除任何的东西都不会互相影响。

registry 把所有的 CodeGenProcessor 都 load 出来，放到一个注册中心里面，把要处理的类和注解都放到一个地方，将来方便重复使用。


模板是通过工具包生成的